// 「闭包」是对「对象」拙劣的模仿
// 「对象」是对「闭包」拙劣的模仿

const xiaowang = makePerson('xiaowang');
const xiaoli = makePerson('xiaoli');

const xiaoliu = {
  name: 'xiaoliu',
  sayHello() {
    console.log(this.name, 'wang wang wang');
  },
};

function makePerson(name) {
  const obj = {
    name,
    sayHello() {
      console.log('Hi, I am', obj.name);
    },
  };
  return obj;
}

makePerson.abc = 3;
console.log(makePerson.abc);

// 蓝图
function Person(name) {
  this.name = name;
}
Person.prototype.name = 'default name';
Person.prototype.sayHello = function () {
  console.log('Hi, ', this.name);
};

// 000001 => 0000078 => 000535 => X
// 编程范式
// 1. 命令式
// 2. 函数式
// 3. 面向对象

// 实例 instance
const xiaotong = new Person('xiaotong'); // xiaotong.__proto__ => {constructor:{}}
const xiaopiao = new Person('xiaotong');
// xiaotong.sayHello();

console.log(xiaotong.sayHello());

// 1. 创建一个新对象
// 2. this 指向这个新对象
// 3. 执行构造函数中的代码
// 4. 返回新对象
const obj = new Object(); // const obj = {}
const arr = new Array(); // const arr = []
const date = new Date();
const fn = new Function();

// 每一个函数都有一个公共车间 叫做 prototype
function Fnc() {
  console.log('so sth');
}
Fnc.prototype.str = 'str';
Fnc.prototype.num = 42;
Fnc.prototype.hey = function hey() {
  console.log('hey');
};
const xiaotao = new Fnc();
xiaotao.str = 'ABC';
console.log('here!!!!', xiaotao.str);
xiaotao.hey();

// 每一个对象都有一份文件 证明自己是谁创造的、有哪些创造者留给自己的内容 叫做[[prototype]] => __proto__
const shan = {
  miao: {
    lao: shan,
  },
};
shan.yyyyyy = 123;

function Dog(name) {
  this.name = name;
}
// {c}
Dog.prototype = {};
// {}

const ahuang = new Dog('ahuang');
const jiujiu = new Dog('jiujiu');
ahuang.greet();
jiujiu.greet();
jiujiu.greet = function () {
  console.log('jiujiu wangwangwang');
};
jiujiu.greet();
